package com.nulldev.util.io.throttling;

import java.io.IOException;
import java.io.InputStream;

/**
 * An output stream that is bandwidth-throttled by a {@link BandwidthThrottler}.
 * It redirects all write calls to the throttler.
 */
public class BandwidthThrottledInputStream extends InputStream {
	private final InputStream inputStream;
	private final BandwidthThrottler throttler;

	public BandwidthThrottledInputStream(final InputStream inputStream, final BandwidthThrottler throttler) {
		this.inputStream = inputStream;
		this.throttler = throttler;
	}

	@Override
	public int read() throws IOException {
		return this.inputStream.read();
	}

	@Override
	public int read(final byte[] b) throws IOException {
		final int allowedBytesToRead = throttler.getAllowedBytes(b.length);
		return this.inputStream.read(b, 0, allowedBytesToRead);
	}

	@Override
	public int read(final byte[] b, final int off, final int len) throws IOException {
		final int allowedBytesToRead = throttler.getAllowedBytes(b.length - off);
		return this.inputStream.read(b, off, allowedBytesToRead);
	}

	@Override
	public synchronized void reset() throws IOException {
		this.inputStream.reset();
	}

	@Override
	public int available() throws IOException {
		return this.inputStream.available();
	}

	@Override
	public long skip(final long n) throws IOException {
		return this.inputStream.skip(n);
	}

	@Override
	public boolean markSupported() {
		return this.inputStream.markSupported();
	}

	@Override
	public synchronized void mark(final int readlimit) {
		this.inputStream.mark(readlimit);
	}

	@Override
	public void close() throws IOException {
		this.inputStream.close();
	}
}